package com.iwthings.x264;

import java.net.InetAddress;
import java.net.UnknownHostException;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Rect;
import android.graphics.Bitmap.Config;
import android.hardware.Camera;
import android.hardware.Camera.ErrorCallback;
import android.util.Log;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.SurfaceHolder.Callback;

public class X264Player implements SurfaceHolder.Callback, ErrorCallback {
	SurfaceView m_surfaceview = null;
	SurfaceHolder m_surfacehold = null;
	int iret = 0;
	Bitmap bmp = null;
	int width = 0;
	int height = 0;
	ThreadDrawImage thdraw = null;
	ThreadDecode thdecode = null;

	public int OpenDecoder(int userid, String ip, int port,
			SurfaceView surfaceview) {
		String strip;

		try {
			InetAddress myServer = InetAddress.getByName(ip);
			strip = myServer.getHostAddress();
			Log.i("mediacodec", ip);

		} catch (UnknownHostException e) {
			// TODO Auto-generated catch block
			strip = "124.202.151.53";
		}
		m_surfaceview = surfaceview;
		m_surfacehold = m_surfaceview.getHolder(); // 绑定SurfaceView，取得SurfaceHolder对象
		m_surfacehold.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
		m_surfacehold.addCallback((Callback) this);

		iret = X264Jni.GetInstance().OpenX264Decode(userid, strip, port);
		if (iret < 0) {
			return -1;
		}

		thdecode = new ThreadDecode();
		thdecode.start();

		thdraw = new ThreadDrawImage();
		thdraw.start();

		return 0;
	}

	public void CloseDecoder() {
		if (thdraw != null) {
			while (thdraw.isAlive()) {
				thdraw.interrupt();
			}
			thdraw = null;
		}

		X264Jni.GetInstance().CloseX264Decoder();
		if (thdecode != null) {
			while (thdecode.isAlive())
				;
			{
				thdecode.interrupt();
			}

			thdecode = null;
		}
	}

	@Override
	public void onError(int error, Camera camera) {
		// TODO Auto-generated method stub

	}

	@Override
	public void surfaceChanged(SurfaceHolder holder, int format, int width,
			int height) {
		// TODO Auto-generated method stub

	}

	@Override
	public void surfaceCreated(SurfaceHolder holder) {

	}

	@Override
	public void surfaceDestroyed(SurfaceHolder holder) {
		CloseDecoder();
	}

	class ThreadDecode extends Thread {
		public void run() {
			X264Jni.GetInstance().x264Decoder();
		}
	}

	class ThreadDrawImage extends Thread {
		Rect src;
		Rect dst;

		public void run() {
			while (!this.isInterrupted()) {
				try {
					Thread.sleep(30);
				} catch (Exception e) {
					e.printStackTrace();
				}

				if (bmp == null) {
					width = X264Jni.GetInstance().GetWidth();
					height = X264Jni.GetInstance().GetHeight();
					if (width <= 0 || height <= 0) {
						continue;
					}

					src = new Rect(0, 0, width, height);
					dst = new Rect(0, 0, m_surfaceview.getWidth(),
							m_surfaceview.getHeight());
					if (dst.width() == 0 || dst.height() == 0) {
						continue;
					}
					bmp = Bitmap.createBitmap(width, height, Config.RGB_565);
					if (bmp == null) {
						continue;
					}
				}
				// fill bitmap
				X264Jni.GetInstance().Render(bmp);

				Canvas canvas = m_surfacehold.lockCanvas();
				if (canvas == null) {
					continue;
				}
				canvas.drawBitmap(bmp, src, dst, null);
				m_surfacehold.unlockCanvasAndPost(canvas);
			}
		}
	}

}
